﻿using GalaSoft.MvvmLight;
using GalaSoft.MvvmLight.Command;
using Syncfusion.XForms.RichTextEditor;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.IO;
using System.Runtime.CompilerServices;
using System.Threading.Tasks;
using System.Windows.Input;
using TabbedTemplate.Models;
using TabbedTemplate.Services;
using Xamarin.Forms;

namespace TabbedTemplate.ViewModels
{
    public class PunchPageViewModel : ViewModelBase, INotifyPropertyChanged
    {

        public new event PropertyChangedEventHandler PropertyChanged;

        public void RaisePropertyChange(
            [CallerMemberName] string propertyname = null)
        {
            PropertyChanged?.Invoke(this,
                new PropertyChangedEventArgs(propertyname));
        }
        /// <summary>
        /// 导航参数。
        /// </summary>
        public PunchTimeStampParameter PunchTimeStampParameter
        {
            get => _punchTimeStampParameter;
            set =>
                Set(nameof(PunchTimeStampParameter),
                    ref _punchTimeStampParameter, value);
        }
        private PunchTimeStampParameter _punchTimeStampParameter;




        /// <summary>
        /// ImageViewModel容器。
        /// </summary>
        private ObservableCollection<ImageViewModel> _imageViewModelCollection;
        public ObservableCollection<ImageViewModel> ImageViewModelCollection
        {
            get => _imageViewModelCollection;
            set =>
                Set(nameof(ImageViewModelCollection),
                    ref _imageViewModelCollection, value);
        }

        private const string FileName = "Test.jpg";
        private static readonly string ImagePath =
            Path.Combine(
                Environment.GetFolderPath(Environment.SpecialFolder
                    .LocalApplicationData), FileName);

        //******** 绑定属性

        /// <summary>
        /// 图片插入命令。
        /// </summary>
        public ICommand ImageInsertCommand { get; set; }
        /// <summary>
        /// 富文本内容。
        /// </summary>
        public string EditorHtmlText
        {
            get => _editorHtmlText;
            set => Set(nameof(EditorHtmlText), ref _editorHtmlText, value);
        }
        private string _editorHtmlText;

        /// <summary>
        /// 图片Byte。
        /// </summary>
        public byte[] ImageSource
        {
            get => _imageSource;
            set => Set(nameof(ImageSource), ref _imageSource, value);
        }
        private byte[] _imageSource;


        public bool IsVisualCollectionView { get; set; }

        private ObservableCollection<object> _toolBarItems;

        public ObservableCollection<object> ToolBarItems
        {
            get => _toolBarItems;
            set => Set(nameof(ToolBarItems), ref _toolBarItems, value);
        }

        // ******** 依赖注入。
        private readonly IPunchNavigationService _punchNavigationService;
        private readonly IDrawPicService _drawPicService;
        private readonly IPhotoPickerService _photoPickerService;
        private readonly IAlertService _alertService;
        private readonly IImageService _imageService;
        private readonly IPunchInfoStorage _punchInfoStorage;
        private readonly IStoreStorage _storeStorage;
        private readonly IPickPhotoService _pickPhotoService;
        private readonly IPreferenceStorage _preferenceStorage;
        public PunchPageViewModel(IPhotoPickerService photoPickerService,
            IAlertService alertService, IImageService imageService,
            IPunchInfoStorage punchInfoStorage, IStoreStorage storeStorage,
            IPickPhotoService pickPhotoService, IPreferenceStorage preferenceStorage, IDrawPicService drawPicService, IPunchNavigationService punchNavigationService)
        {
            ImageViewModelCollection =
                new ObservableCollection<ImageViewModel>();
            EditorHtmlText = "";
            RaisePropertyChange($"EditorHtmlText");
            _photoPickerService = photoPickerService;
            ImageInsertCommand = new Command<object>(Load);
            _alertService = alertService;
            _punchNavigationService = punchNavigationService;
            _imageService = imageService;
            _punchInfoStorage = punchInfoStorage;
            _storeStorage = storeStorage;
            _pickPhotoService = pickPhotoService;
            _preferenceStorage = preferenceStorage;
            _drawPicService = drawPicService;
            ToolBarItems = new ObservableCollection<object> {
                ToolbarOptions.Bold,
                ToolbarOptions.Italic,
                ToolbarOptions.Underline,
                ToolbarOptions.FontColor,
                ToolbarOptions.HighlightColor,
                ToolbarOptions.FontSize,
                ToolbarOptions.ParagraphFormat,
                ToolbarOptions.BulletList,
                ToolbarOptions.NumberList,
                ToolbarOptions.Alignment,
                ToolbarOptions.IncreaseIndent,
                ToolbarOptions.DecreaseIndent,
                ToolbarOptions.Hyperlink,
                ToolbarOptions.ClearFormat
            };
            RaisePropertyChange($"ToolBarItems");

        }


        // ******** 绑定命令。

        private RelayCommand _pageAppearingCommand;

        public RelayCommand PageAppearingCommand =>
            _pageAppearingCommand ??=
                new RelayCommand(PageAppearingCommandFunction);

        public void PageAppearingCommandFunction()
        {
            if (!_preferenceStorage.Get("newPunch", true))
            {
                return;
            }
            ImageViewModelCollection.Clear();
            RaisePropertyChange($"ImageViewModelCollection");
            IsVisualCollectionView = false;
            RaisePropertyChange($"IsVisualCollectionView");
            EditorHtmlText = PunchTimeStampParameter.PunchInfo.Content;
            RaisePropertyChange($"EditorHtmlText");

        }

        /// <summary>
        /// Creates a event args for Image Insert
        /// </summary>
        void Load(object obj)
        {
            ImageInsertedEventArgs imageInsertedEventArgs =
                (obj as ImageInsertedEventArgs);
            this.GetImage(imageInsertedEventArgs);
        }

        /// <summary>
        /// Gets image stream from picker using dependency service.
        /// </summary>
        /// <param name="imageInsertedEventArgs">Event args to be passed for dependency service</param>
        public async void GetImage(ImageInsertedEventArgs imageInsertedEventArgs)
        {
            Stream imageStream =
                await _photoPickerService.GetImageStreamAsync();
            Syncfusion.XForms.RichTextEditor.ImageSource imageSource =
                new Syncfusion.XForms.RichTextEditor.ImageSource();
            if (imageStream == null)
            {
                return;
            }

            imageSource.ImageStream = imageStream;
            imageInsertedEventArgs.ImageSourceCollection.Add(imageSource);
        }




        /// <summary>
        /// 打卡命令
        /// 1.存储内容
        /// 2.增加一条打卡历史记录
        /// 3.弹出弹窗。
        /// </summary>
        private RelayCommand _punchCommand;

        public RelayCommand PunchCommand =>
            _punchCommand ??=
                new RelayCommand(async () => await PunchCommandFunction());

        public async Task PunchCommandFunction()
        {

            //弹出弹窗，询问是否确认打卡
            var result =
                await _alertService.ShowAlert("提示", "是否确认打卡？", "确认", "取消");

            if (result)
            {

                if (!_punchInfoStorage.PunchInfoStorageInitialized())
                {
                    await _punchInfoStorage.PunchInfoStorageInitializeAsync();
                }

                var resLong = await _punchInfoStorage.InsertPunchInfoAsync(PunchTimeStampParameter.Store.Uid,
                    EditorHtmlText);
                if (!_storeStorage.UserCacheInitialized())
                {
                    await _storeStorage.UserCacheInitializeAsync();
                }

                //创建文件夹
                _imageService.CreateFolder(resLong);
                for (var i = 0; i < ImageViewModelCollection.Count; i++)
                {
                    await _imageService.SaveImageAsync(resLong,
                        ImageViewModelCollection[i].ImageSource, resLong + "-" + i + ".png");
                }

                await _storeStorage.InsertAStore(PunchTimeStampParameter.Store);
                _alertService.ShowAlert("提示", "打卡成功!", "确认");
                EditorHtmlText = "";
                RaisePropertyChange($"EditorHtmlText");
                await _punchNavigationService.NavigateBack();
            }
        }


        /// <summary>
        /// 生成长图命令。
        /// </summary>
        private RelayCommand _picCommand;
        public RelayCommand PicCommand =>
            _picCommand ??=
                new RelayCommand(async () => await PicCommandFunction());

        public async Task PicCommandFunction()
        {
            IList<byte[]> localPictures = new List<byte[]>();
            for (int i = 0; i < ImageViewModelCollection.Count; i++)
            {
                localPictures.Add(ImageViewModelCollection[i].ImageSource);
            }
            DrawContent drawContent = new DrawContent
            {
                Content = EditorHtmlText,
                Pictures = localPictures
            };
            await _punchNavigationService.NavigateToAsync(ContentNavigationConstant.DrawPicPage, drawContent);
        }
        //public async Task PicCommandFunction() {
        //    var res =
        // .CurrentPage.FindByName<ScrollView>("MyPic");
        //    var res1= MainPage.CurrentPage.FindByName<CarouselView>("CV");
        //    await _imageService.Capture();
        //}



        /// <summary>
        /// Correcting void elements in the HTML. 
        /// </summary>
        /// <param name="inputString">HTML string with void HTML elements</param>
        /// <returns>This method make your HTML to pass the DocIO HTML validation</returns>
        private string IgnoreVoidElementsInHtml(string inputString)
        {
            inputString = inputString.Replace(
                "<meta http-equiv=\"Content-Type\" content=\"application/xhtml+xml; charset=utf-8\">",
                "");
            inputString = inputString.Replace("<br>", "<br/>");
            inputString = inputString.Replace("\n", "");
            inputString = inputString.Replace("\r", "");
            inputString = inputString.Replace("<title></title>", "");
            inputString = inputString.Replace(
                "﻿<?xml version=\"1.0\" encoding=\"utf-8\"?><!DOCTYPE html PUBLIC" +
                " \"-//W3C//DTD XHTML 1.1//EN\" \"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd\">",
                "");
            return inputString;
        }


        /// <summary>
        /// ViewModel in ViewModel,实现在CollectionView中动态添加图片并执行操作。
        /// </summary>
        /// <param name="imageViewModel"></param>
        /// <returns></returns>
        public async Task AddImageViewModel(ImageViewModel imageViewModel)
        {
            _preferenceStorage.Set("newPunch", false);
            int index = ImageViewModelCollection.IndexOf(imageViewModel);
            int count = ImageViewModelCollection.Count;
            if (imageViewModel.ImageSource == null)
            {
                var res = await _alertService.ShowAlert("请选择一种方式", "取消", null,
                    "拍照", "从本地相册选取一张照片", null);
                switch (res)
                {
                    case "拍照": _imageSource = await _pickPhotoService.TakePhotoAsync(); break;
                    case "从本地相册选取一张照片": _imageSource = await _pickPhotoService.PickPhotoAsync(); break;
                }
                if (_imageSource == null)
                {
                    return;
                }
            }
            else
            {
                return;
            }
            //TODO SAVE
            ImageViewModelCollection.Add(new ImageViewModel(this, null));
            IsVisualCollectionView = true;
            RaisePropertyChange($"IsVisualCollectionView");
        }

        public void RemoveImageViewModel(ImageViewModel imageViewModel)
        {
            _preferenceStorage.Set("newPunch", false);
            ImageViewModelCollection.Remove(imageViewModel);
            if (ImageViewModelCollection.Count == 0)
            {
                IsVisualCollectionView = false;
                RaisePropertyChange($"IsVisualCollectionView");
            }
        }
    }
}
